    //
//  BaseRefreshController.m
//  Postre
//
//  Created by CoderLT on 2017/5/24.
//  Copyright © 2017年 CoderLT. All rights reserved.
//

#import "BaseRefreshController.h"
#import <KVOController/KVOController.h>
#import "ATHttpTool.h"

@interface BaseRefreshController () {
    BOOL _isSetKVO;
    BOOL _needReload;
    __weak UIView *_emptyView;
}
@property (nonatomic, weak) UIScrollView *scrollView;
@property (nonatomic, assign) NSInteger currentPage;
@property (nonatomic, assign) BOOL isRefreshing;
@property (nonatomic, copy) NSString *emptyTitle;
@property (nonatomic, strong) UIImage *emptyImage;
@property (nonatomic, strong) UIImage *noNetImage;

@end

@implementation BaseRefreshController
- (instancetype)init {
    if (self = [super init]) {
        _refreshFormBackground = NO;
        _refreshDidAppear = NO;
        _refreshWillAppear = NO;
        _appDidEnterBackgroundDate = [NSDate date];
    }
    return self;
}
- (void)viewDidLoad {
    [super viewDidLoad];
    // Do any additional setup after loading the view.
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(br_appWillEnterForegroundNotificationHandle) name:UIApplicationWillEnterForegroundNotification object:nil];
    [[NSNotificationCenter defaultCenter] addObserver:self
                                             selector:@selector(br_applicationDidEnterBackgroundNotificationHandle) name:UIApplicationDidEnterBackgroundNotification object:nil];
}
- (void)viewWillAppear:(BOOL)animated {
    [super viewWillAppear:animated];
    if (self.refreshWillAppear || (self.refreshWillAppearIfFirstPage && self.isAtFirstPage)) {
        [self headerRefreshingIfNeed];
    }
}
- (void)viewDidAppear:(BOOL)animated {
    [super viewDidAppear:animated];
    if (self.refreshDidAppear || (self.refreshDidAppearIfFirstPage && self.isAtFirstPage)) {
        [self headerRefreshingIfNeed];
    }
}
- (BOOL)isAtFirstPage {
    return (self.currentPage == RefreshPageStart || self.scrollView.contentOffset.y <= NAVI_HIGHT);
}
- (void)br_appWillEnterForegroundNotificationHandle {
    [self applicationWillEnterBackground:self.appDidEnterBackgroundDate];
    if (self.refreshFormBackground && self.viewIsAppear) {
        if (self.lastRefreshDate.timeIntervalSinceNow < -300) {
            [self headerRefreshing];
        }
        else {
            [self headerRefreshingIfNeed];
        }
    }
}
- (void)br_applicationDidEnterBackgroundNotificationHandle {
    self.appDidEnterBackgroundDate = [NSDate date];
    [self applicationDidEnterBackground];
}
- (void)applicationWillEnterBackground:(NSDate *)enterDate { }
- (void)applicationDidEnterBackground { }

- (void)dealloc {
    _scrollView.delegate = nil;
    [[NSNotificationCenter defaultCenter] removeObserver:self name:UIApplicationWillEnterForegroundNotification object:nil];
}


#pragma mark - refresh 刷新处理
- (void)setupRefresh:(UIScrollView *)scrollView option:(ATRefreshOption)option {
    self.scrollView = scrollView;
    if (option & ATHeaderRefresh) {
        MJRefreshNormalHeader *header = [MJRefreshNormalHeader headerWithRefreshingTarget:self refreshingAction:@selector(headerRefreshing)];
        header.automaticallyChangeAlpha = YES;
        header.lastUpdatedTimeLabel.hidden = YES;
        
        if (option & ATHeaderAutoRefresh) {
            [self headerRefreshing];
        }
        else if (option & ATHeaderAutoRefreshVisible) {
            [header beginRefreshing];
        }
        scrollView.mj_header = header;
    }
    
    if (option & ATFooterRefresh) {
        MJRefreshAutoNormalFooter *footer = [MJRefreshAutoNormalFooter footerWithRefreshingTarget:self refreshingAction:@selector(footerRefreshing)];
        footer.triggerAutomaticallyRefreshPercent = -10.0f;
        
        if (option & ATFooterAutoRefresh) {
            [self footerRefreshing];
        }
        else if (option & ATFooterAutoRefreshVisible) {
            [footer beginRefreshing];
        }
        else if (option & ATFooterDefaultHidden) {
            footer.hidden = YES;
        }
        scrollView.mj_footer = footer;
    }
}

- (void)headerRefreshingIfNeed {
    if (!self.isRefreshing
        && self.haveDidAppearFirst
        && self.currentPage == RefreshPageStart) {
        [self headerRefreshing];
    }
}
- (void)scroolToTopBeginRefresh {
    if (!self.scrollView.mj_header.isRefreshing) {
        [self.scrollView.mj_header beginRefreshing];
        dispatch_async_on_main_queue(^{
            [self.scrollView scrollToTopAnimated:NO];
        });
    }
}
- (void)headerRefreshing {
    self.isRefreshing = YES;
    self.scrollView.mj_footer.hidden = YES;
    self.currentPage = RefreshPageStart;
    [self refreshData:self.currentPage];
    self.lastRefreshDate = [NSDate date];
}

- (void)footerRefreshing {
    self.currentPage++;
    [self refreshData:self.currentPage];
}

- (void)endRefreshFailure {
    if (self.currentPage > RefreshPageStart) {
        self.currentPage--;
    }
    [self baseEndRefreshing];
}
- (void)baseEndRefreshing {
    if (self.scrollView.mj_header.isRefreshing) {
        [self.scrollView.mj_header endRefreshing];
    }
    self.isRefreshing = NO;
}
- (void)endRefresh:(BOOL)hasMore {
    [self baseEndRefreshing];
    
    if (hasMore) {
        self.scrollView.mj_footer.state = MJRefreshStateIdle;
        ((MJRefreshAutoStateFooter *)self.scrollView.mj_footer).stateLabel.textColor = [UIColor colorWithRGB:0x666666];
        self.scrollView.mj_footer.hidden = NO;
    }
    else {
        self.scrollView.mj_footer.state = MJRefreshStateNoMoreData;
        ((MJRefreshAutoStateFooter *)self.scrollView.mj_footer).stateLabel.textColor = [UIColor colorWithRGB:0x999999];
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(0.001 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            self.scrollView.mj_footer.hidden = (self.currentPage == RefreshPageStart) || (self.scrollView.contentSize.height < self.scrollView.height);
        });
    }
}
- (void)endRefreshNeedHidden:(BOOL)hasMore {
    [self baseEndRefreshing];
    
    self.scrollView.mj_footer.state = hasMore ? MJRefreshStateIdle : MJRefreshStateNoMoreData;
    self.scrollView.mj_footer.hidden = !hasMore;
}

- (void)refreshData:(NSInteger)page {
    self.currentPage = page;
    
    if ([self.className isEqualToString:[BaseRefreshController className]]) {
        dispatch_after(dispatch_time(DISPATCH_TIME_NOW, (int64_t)(1 * NSEC_PER_SEC)), dispatch_get_main_queue(), ^{
            if (self.scrollView.mj_header.isRefreshing || self.scrollView.mj_footer.isRefreshing) {
                [self endRefreshFailure];
            }
        });
    }
}

- (void)setIsRefreshing:(BOOL)isRefreshing {
    _isRefreshing = isRefreshing;
    
    [self.scrollView reloadEmptyDataSet];
}


#pragma mark - DZNEmptyData 空数据界面处理
- (void)setupEmpty:(UIScrollView *)scrollView {
    [self setupEmpty:scrollView image:[UIImage imageNamed:@"DefaultNoData"] title:@"空空如也~"];
}
- (void)setupEmpty:(UIScrollView *)scrollView image:(UIImage *)image title:(NSString *)title {
    scrollView.emptyDataSetSource = self;
    scrollView.emptyDataSetDelegate = self;
    self.emptyImage = image;
    self.emptyTitle = title;

    if (_isSetKVO) {
        return;
    }
    _isSetKVO = YES;
    [self.KVOController observe:scrollView keyPaths:@[FBKVOKeyPath(scrollView.contentSize), FBKVOKeyPath(scrollView.contentInset)] options:NSKeyValueObservingOptionNew block:^(id  _Nullable observer, UIScrollView * _Nonnull object, NSDictionary<NSString *,id> * _Nonnull change) {
        if (object.contentOffset.y >= -object.mj_inset.top) {
            [object performSelector:@selector(reloadEmptyDataSet) afterDelay:0.01f];
        }
    }];
}

- (NSAttributedString *)titleForEmptyDataSet:(UIScrollView *)scrollView {
    NSMutableParagraphStyle *paragraph = [NSMutableParagraphStyle new];
    paragraph.lineBreakMode = NSLineBreakByWordWrapping;
    paragraph.alignment = NSTextAlignmentCenter;
    NSDictionary* attributes = @{NSFontAttributeName : [UIFont systemFontOfSize:14.0f],
                                 NSForegroundColorAttributeName : [UIColor colorWithRGB:0x999999],
                                 NSParagraphStyleAttributeName : paragraph};
    NSString *text = self.isRefreshing ? @"数据更新中..." : self.emptyTitle;
    if (![ATHttpTool reachable]) {
        text = MPNoNetworkMsg;
    }
    return [[NSMutableAttributedString alloc] initWithString:(text ? [NSString stringWithFormat:@"\r\n%@", text] : @"")
                                                  attributes:attributes];
}
- (NSAttributedString *)descriptionForEmptyDataSet:(UIScrollView *)scrollView {
    return nil;
}
- (UIImage *)imageForEmptyDataSet:(UIScrollView *)scrollView {
    return [ATHttpTool reachable] ? self.emptyImage : [UIImage imageNamed:@"DefaultNoNetwork"];
}
- (CAAnimation *)imageAnimationForEmptyDataSet:(UIScrollView *)scrollView {
    return nil;
}
- (NSAttributedString *)buttonTitleForEmptyDataSet:(UIScrollView *)scrollView forState:(UIControlState)state {
    return nil;
}
- (UIImage *)buttonBackgroundImageForEmptyDataSet:(UIScrollView *)scrollView forState:(UIControlState)state {
    return nil;
}
- (UIColor *)backgroundColorForEmptyDataSet:(UIScrollView *)scrollView {
    return nil;
}
- (CGFloat)verticalOffsetForEmptyDataSet:(UIScrollView *)scrollView {
    UIEdgeInsets inset = scrollView.mj_header ? scrollView.mj_header.scrollViewOriginalInset : scrollView.contentInset;
    if (kIsiPhoneX && inset.bottom == TAB_BAR_ADDING) {
        inset.bottom = 0;
    }
    CGFloat contentSizeHeight =  scrollView.contentSize.height;
    if (contentSizeHeight == 35.0f) {
        contentSizeHeight = 0;
    }
    if ([scrollView.className isEqualToString:@"WKScrollView"]) {
        contentSizeHeight = 0;
    }
    else if ([scrollView isKindOfClass:[UICollectionView class]]) {
        UICollectionViewFlowLayout *layout = (UICollectionViewFlowLayout *)(((UICollectionView *)scrollView).collectionViewLayout);
        if ([layout respondsToSelector:@selector(scrollDirection)]) {
            if (layout.scrollDirection == UICollectionViewScrollDirectionHorizontal) {
                contentSizeHeight = 0;
            }
        }
    }
    if (!_emptyView || _emptyView.superview != scrollView) {
        _emptyView = nil;
        [scrollView.subviews enumerateObjectsUsingBlock:^(__kindof UIView * _Nonnull obj, NSUInteger idx, BOOL * _Nonnull stop) {
            if ([obj.className isEqualToString:@"DZNEmptyDataSetView"]) {
                _emptyView = obj;
                *stop = YES;
            }
        }];
        if (_emptyView.clipsToBounds) {
            _emptyView.clipsToBounds = NO;
        }
    }
    CGFloat offset = inset.top + contentSizeHeight + (scrollView.height - inset.top - contentSizeHeight - inset.bottom) * 0.4f - scrollView.height * 0.5f - ((CGPoint)([_emptyView convertPoint:CGPointZero toView:self.scrollView.superview])).y;
    if (scrollView.mj_header.isRefreshing) {
        offset += MJRefreshHeaderHeight;
    }
    return offset;
}
- (CGFloat)spaceHeightForEmptyDataSet:(UIScrollView *)scrollView {
    return 1;
}

- (BOOL)emptyDataSetShouldDisplay:(UIScrollView *)scrollView {
    return YES;
}
- (BOOL)emptyDataSetShouldAllowTouch:(UIScrollView *)scrollView {
    return YES;
}
- (BOOL)emptyDataSetShouldAllowScroll:(UIScrollView *)scrollView {
    return YES;
}
- (BOOL)emptyDataSetShouldAnimateImageView:(UIScrollView *)scrollView {
    return NO;
}
- (void)emptyDataSet:(UIScrollView *)scrollView didTapView:(UIView *)view {
    if (!self.isRefreshing && [ATHttpTool reachable]) {
        [self headerRefreshing];
    }
}
- (void)emptyDataSet:(UIScrollView *)scrollView didTapButton:(UIButton *)button {
}
@end
